package com.hsu.yupao.config;

import org.springframework.stereotype.Component;

import javax.servlet.ServletRequestEvent;
import javax.servlet.ServletRequestListener;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import javax.websocket.HandshakeResponse;
import javax.websocket.server.HandshakeRequest;
import javax.websocket.server.ServerEndpointConfig;
import javax.websocket.server.ServerEndpointConfig.Configurator;

/**
 * 从WebSocket中获取用户Session的配置器。
 * 该类用于在WebSocket握手期间将HTTP Session的内容注入到WebSocket的ServerEndpointConfig中，
 * 使得WebSocket session能够访问登录用户的Session信息。
 * @ClassName: HttpSessionConfig
 * @author Hsu琛君珩
 * @date 2024-06-03
 * @apiNote
 * @Version: v1.0
 */
@Component
public class HttpSessionConfig extends Configurator implements ServletRequestListener {

    /**
     * 当一个请求到达并且即将进入处理阶段时调用此方法。
     * 此方法从传入的HTTP请求中获取HTTP session。
     * @param sre 提供关于请求事件的信息。
     */
    @Override
    public void requestInitialized(ServletRequestEvent sre) {
        HttpSession session = ((HttpServletRequest) sre.getServletRequest()).getSession();
    }

    /**
     * 在WebSocket握手请求期间修改握手。这个方法允许我们在WebSocket session中注入HTTP session的数据。
     * 如果HTTP session存在，则将其添加到WebSocket的配置中，使得WebSocket server endpoint可以访问用户的HTTP session数据。
     * @param sec WebSocket server endpoint的配置。
     * @param request 握手请求，包括访问HTTP session的能力。
     * @param response 握手响应。
     */
    @Override
    public void modifyHandshake(ServerEndpointConfig sec, HandshakeRequest request, HandshakeResponse response) {
        HttpSession httpSession = (HttpSession) request.getHttpSession();
        if (httpSession != null) {
            sec.getUserProperties().put(HttpSession.class.getName(), httpSession);
        }
        super.modifyHandshake(sec, request, response);
    }

    /**
     * 在请求处理完毕后，即将从应用服务器中销毁请求对象时调用此方法。
     * 此方法用于执行清理操作，如释放资源、记录日志等。在这里通常不需要实现任何功能。
     * @param arg0 提供关于请求事件的信息，不使用。
     */
    @Override
    public void requestDestroyed(ServletRequestEvent arg0) {
        // 这个方法在HTTP请求结束时调用，这里不需要实现。
    }

}
